﻿//using System;
//using System.Text.RegularExpressions;
//using Newtonsoft.Json.Linq;

//namespace XActivity
//{
//    public class XValidationRule
//    {
//        public string type { get; set; }
//        public bool? required { get; set; }
//        public string pattern { get; set; }
//        public double? max { get; set; }
//        public double? min { get; set; }
//        public int? length { get; set; }

//        public string message { get; set; }
//        public string validator { get; set; }
//    }

//    public class XValidator
//    {
//        public string message { get; set; }

//        public bool IsValid(string key, JObject data, XValidationRule rule)
//        {
//            message = string.IsNullOrWhiteSpace(rule.message) ? "Validation error on field " + key : rule.message;
//            var token = data.GetValue(key);

//            //required
//            //The required rule property indicates that the field must exist on the source object being validated.
//            if ((rule.required ?? false) && token == null) return false;
//            if (token == null) token = JToken.FromObject(string.Empty);

//            //type
//            if (!v_type(token, rule.type)) return false;

//            //pattern
//            //The pattern rule property indicates a regular expression that the value must match to pass validation
//            if (!string.IsNullOrWhiteSpace(rule.pattern) && !v_pattern(token, rule.pattern)) return false;

//            //length
//            if (!v_length(token, rule.length)) return false;

//            //min
//            if (!v_min(token, rule.min)) return false;

//            //max
//            if (!v_max(token, rule.max)) return false;

//            //todo            a
//            //maxLength
//            // if (!v_maxLength(token, rule.max)) return false;

//            //minLength
//            // if (!v_minLength(token, rule.max)) return false;

//            //validator
//            if (!v_validator(token, data, rule.validator, out var msg))
//            {
//                message = msg;
//                return false;
//            }
//            message = string.Empty;
//            return true;
//        }

//        private bool v_pattern(JToken token, string pattern)
//        {
//            return Regex.IsMatch(token.ToString(), pattern);
//        }

//        private bool v_type(JToken token, string type)
//        {
//            if (string.IsNullOrEmpty(type)) return true;
//            switch (type)
//            {
//                case "string":
//                    return token.Type == JTokenType.String;

//                case "integer":
//                    return token.Type == JTokenType.Integer;

//                case "float":
//                    return token.Type == JTokenType.Float;

//                case "number":
//                    return token.Type == JTokenType.Float || token.Type == JTokenType.Integer;

//                case "boolean":
//                    return token.Type == JTokenType.Boolean;

//                case "array":
//                    return token.Type == JTokenType.Array;

//                case "date":
//                    return token.Type == JTokenType.Date;

//                case "email":
//                    return v_pattern(token, @"^\w+([-+.]\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*$");

//                case "url":
//                    return v_pattern(token, @"^http://([\w-]+\.)+[\w-]+(/[\w-./?%&=]*)?$");

//                case "object"://Must be of type object and not Array.isArray.
//                    return token.Type == JTokenType.Object;

//                case "any":
//                default:// Can be any type.
//                    return true;
//            }
//        }

//        private bool v_length(JToken token, int? length)
//        {
//            if (length == null) return true;

//            switch (token.Type)
//            {
//                case JTokenType.String:
//                    return length == token.ToString().Length;

//                case JTokenType.Array:
//                    return token is JArray array ? length == array.Count : false;

//                case JTokenType.Integer:
//                    return length == token.Value<int>();

//                default:
//                    return true;
//            }
//        }

//        private bool v_min(JToken token, int? min)
//        {
//            if (min == null) return true;
//            switch (token.Type)
//            {
//                case JTokenType.String:
//                    return min <= token.ToString().Length;

//                case JTokenType.Array:
//                    return token is JArray array && min <= array.Count;

//                case JTokenType.Integer:
//                    return min <= token.Value<int>();

//                case JTokenType.Float:
//                    return min <= token.Value<float>();

//                default:
//                    return true;
//            }
//        }

//        private bool v_max(JToken token, int? max = 0)
//        {
//            if (max == null) return true;
//            switch (token.Type)
//            {
//                case JTokenType.String:
//                    return max >= token.ToString().Length;

//                case JTokenType.Array:
//                    return token is JArray array && max <= array.Count;

//                case JTokenType.Integer:
//                    return max >= token.Value<int>();

//                case JTokenType.Float:
//                    return max >= token.Value<float>();

//                default:
//                    return true;
//            }
//        }

//        private bool v_validator(JToken token, JObject data, string validator, out string message)
//        {
//            message = string.Empty;
//            if (string.IsNullOrWhiteSpace(validator)) return true;
//            switch (validator)
//            {
//                case "valid_start_time_end":

//                    var start = data.Value<DateTime>("start_time");
//                    if (start == DateTime.MinValue)
//                    {
//                        message = "请设置活动开始和结束时间";
//                        return false;
//                    }
//                    var end = data.Value<DateTime>("end_time");

//                    if (end == DateTime.MinValue)
//                    {
//                        message = "请设置活动开始和结束时间";
//                        return false;
//                    }
//                    if (start > end)
//                    {
//                        message = "活动时间设置有误,结束时间应该大于开始时间";
//                        return false;
//                    }
//                    break;
//            }
//            return true;
//        }
//    }
//}